/*
 * Copyright (c) 2002 Boris Pruessmann and others. All rights reserved. This
 * program and the accompanying materials are made available under the terms of
 * the Common Public License v0.5 which accompanies this distribution, and is
 * available at http://www.eclipse.org/legal/cpl-v05.html
 * 
 * Contributors: Boris Pruessmann - Initial implementation.
 */
package net.sourceforge.perforce.ui.model;

import com.google.common.collect.Lists;

import net.sourceforge.perforce.core.PerforceException;
import net.sourceforge.perforce.core.api.IPerforceServer;
import net.sourceforge.perforce.core.resources.RemoteFile;
import net.sourceforge.perforce.core.resources.RemoteFolder;
import net.sourceforge.perforce.core.syncinfo.FolderSyncInfo;
import net.sourceforge.perforce.ui.IPerforceUIConstants;
import net.sourceforge.perforce.ui.PerforceUIPlugin;
import net.sourceforge.perforce.ui.internal.Policy;

import org.eclipse.core.runtime.IAdaptable;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jface.operation.IRunnableWithProgress;
import org.eclipse.jface.preference.IPreferenceStore;
import org.eclipse.jface.resource.ImageDescriptor;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.ui.ISharedImages;
import org.eclipse.ui.internal.WorkbenchPlugin;
import org.eclipse.ui.model.IWorkbenchAdapter;

import java.lang.reflect.InvocationTargetException;
import java.util.List;

/**
 * @version $Revision: 488 $
 * @author <a href="mailto:bpruessmann@users.sourceforge.net">Boris
 *         Pruessmann</a>
 */
public class ProjectContainerElement extends PerforceModelElement implements IWorkbenchAdapter,
    IAdaptable {
  public class FullPathRemoteFolder extends RemoteFolder {
    public FullPathRemoteFolder(IPerforceServer server, RemoteFolder parent,
        FolderSyncInfo syncInfo, String revision) {
      super(server, parent, syncInfo, revision);
    }

    @Override
    public String getName() {
      return getDepotFilename();
    }
  }

  // ---------------------------------------------------------------------------
  // Private Variables

  /** Stores the perforce server. */
  private IPerforceServer server;

  // -------------------------------------------------------------------------
  // Public Constructors

  /** Constructor for ProjectContainerElement. */
  public ProjectContainerElement(IPerforceServer server) {
    this.server = server;
  }

  // ---------------------------------------------------------- Public Methods
  // (IWorkbenchAdapter)

  public Object[] getChildren(Object o) {
    if (!(o instanceof ProjectContainerElement)) {
      return null;
    }

    final List<RemoteFolder> result = Lists.newArrayList();

    Shell shell = new Shell(Display.getDefault());
    try {
      run(true, false, new IRunnableWithProgress() {
        @SuppressWarnings("unused")
        // InterruptedException
        public void run(IProgressMonitor monitor) throws InvocationTargetException,
            InterruptedException {
          IPreferenceStore store = PerforceUIPlugin.getPlugin().getPreferenceStore();
          boolean showFullName =
              store.getBoolean(IPerforceUIConstants.PREF_SHOW_FULLPATH_FOR_PROJECTS);
          try {
            RemoteFile[] files = server.findAllFiles(".project", monitor); //$NON-NLS-1$
            for (int i = 0; i < files.length; i++) {
              String folderName = files[i].getDepotFilename();
              folderName = folderName.substring(0, folderName.lastIndexOf('/'));

              String parentName = folderName.substring(0, folderName.lastIndexOf('/'));
              FolderSyncInfo syncInfo = new FolderSyncInfo(parentName);
              RemoteFolder parent = new RemoteFolder(server, null, syncInfo, "#head"); //$NON-NLS-1$

              syncInfo = new FolderSyncInfo(folderName);
              RemoteFolder folder = createFolder(showFullName, server, parent, syncInfo, "#head"); //$NON-NLS-1$


              result.add(folder);
            }
          } catch (PerforceException e) {
            throw new InvocationTargetException(e);
          }
        }

        private RemoteFolder createFolder(boolean showFullName, IPerforceServer server,
            RemoteFolder parent, FolderSyncInfo syncInfo, String revision) {
          if (showFullName) return new FullPathRemoteFolder(server, parent, syncInfo, revision);
          return new RemoteFolder(server, parent, syncInfo, revision);
        }
      });
    } catch (InvocationTargetException e) {
      handle(e);
    } catch (InterruptedException e) {
      handle(e);
    } finally {
      shell.dispose();
    }

    return result.toArray();
  }

  public ImageDescriptor getImageDescriptor(Object object) {
    if (!(object instanceof ProjectContainerElement)) {
      return null;
    }

    return WorkbenchPlugin.getDefault().getSharedImages().getImageDescriptor(
        ISharedImages.IMG_OBJ_PROJECT);
  }

  public String getLabel(Object o) {
    if (!(o instanceof ProjectContainerElement)) {
      return null;
    }

    return Policy.bind("ProjectContainerElement.getLabel");
  }

  public Object getParent(Object o) {
    return null;
  }

  // ----------------------------------------------------------------- Public
  // Methods (IAdaptable)

  @SuppressWarnings("unchecked")
  // adapter
  public Object getAdapter(Class adapter) {
    if (adapter == IWorkbenchAdapter.class) {
      return this;
    }

    return null;
  }
}
